package pl.ericpol.kernel.schemas;

import java.util.ArrayList;
import java.util.List;
import java.util.Map;

import pl.ericpol.commons.Sign;
import pl.ericpol.environment.devices.Device;
import pl.ericpol.environment.sensors.Sensor;

public class Condition {

	private Map<Device, Integer> devices;
	private Map<Sensor, Object[]> sensors;
	private byte priority;
	private boolean result = true;	
	
	public Condition(Map<Device, Integer> devices,
			Map<Sensor, Object[]> sensors, byte priority) {
		this.devices = devices;
		this.sensors = sensors;
		this.priority = priority;
	}
	
	public Condition(Map<Device, Integer> devices, Map<Sensor, Object[]> sensors) {
		super();
		this.devices = devices;
		this.sensors = sensors;
	}

	public List<Action> run() {
		for (Map.Entry<Sensor, Object[]> entry : sensors.entrySet()) {
			Sensor currSensor = entry.getKey();
			Sign currSign = (Sign) entry.getValue()[0];
			Long currValue = (Long) entry.getValue()[1];
			if (!checkCondition(currSensor, currSign, currValue)) {
				result = false;
				break;
			}
		}
		List<Action> actions = new ArrayList<Action>();
		if (result) {
			for (Map.Entry<Device, Integer> entry : devices.entrySet()) {
				Device device = entry.getKey();
				int value = entry.getValue();
				actions.add(new Action(device, value, priority));
			}
		}
		return actions;
	}

	public boolean checkCondition(Sensor sensor, Sign sign, Long value) {
		Long state = sensor.getState();
		boolean result = false;
		switch (sign) {
		case E:
			if (state == value)
				result = true;
			break;
		case G:
			if (state > value)
				result = true;
			break;
		case GE:
			if (state >= value)
				result = true;
			break;
		case L:
			if (state < value)
				result = true;
			break;
		case LE:
			if (state <= value)
				result = true;
			break;
		case NE:
			if (state != value)
				result = true;
			break;
		}
		return result;
	}

}
